import { getMusicDetailById, getMusicLyric, getMusicPlayUrl } from "@/service/api/musicRequest";
import type { ISearchSongItem } from "@/types/music/searchSongType";
import { composeCLyrics, parseLyric, type IComposeLyrics } from "@/utils/handleLyrics";
import { defineStore } from "pinia";
import { showToast } from "vant";
import { ref, computed } from "vue";

export interface ISongDetail {
  id: number;
  name: string;
  singer: string;
  playUrl: string;
  picUrl: string;
  duration: number;
  LyricList: IComposeLyrics[];
}

const usePlayerStore = defineStore("player", () => {
  const audio = document.querySelector("#audio") as HTMLAudioElement;
  const currentMusic = ref<ISongDetail>(),
    currentTime = ref(0),
    currentLyric = ref({
      index: 0,
      text: "",
      c_text: "",
    }),
    isPlay = ref(false);
  const musicHistoryList = ref<ISearchSongItem[]>([]),
    recommandMusicList = ref<ISearchSongItem[]>([]);

  // 时间百分比
  const currentFormat = computed(() =>
    currentMusic.value ? (((currentTime.value * 1000) / currentMusic.value!.duration) * 100).toFixed(0) : 0
  );

  // 加载音乐
  const loadMusicPlayer = async (id: number) => {
    initCurrent(id);
    if (initCurrent(id)) {
      await getMusicData(id);
      audio.src = currentMusic.value!.playUrl;
      startMusic();
      audio.addEventListener("timeupdate", updateTimeAndLyric);
      audio.addEventListener("ended", musicEnd);
    }
  };

  // 初始化音乐状态
  const initCurrent = (id: number) => {
    if (currentMusic.value && id === currentMusic.value.id) {
      showToast("正在播放该音乐~");
      return false;
    }
    currentMusic.value = {
      id: 0,
      name: "",
      singer: "",
      playUrl: "",
      picUrl: "",
      duration: 0,
      LyricList: [],
    };
    stopMusic();
    // key
    audio.removeEventListener("timeupdate", updateTimeAndLyric);
    audio.removeEventListener("ended", musicEnd);
    audio.src = "";
    return true;
  };

  // 开始/继续播放
  const startMusic = () => {
    audio.play();
    isPlay.value = true;
  };

  // 暂停播放
  const stopMusic = () => {
    audio.pause();
    isPlay.value = false;
  };

  // 拖动进度跳转音乐
  const skipMusic = (setTime: number) => {
    const current = (currentMusic.value!.duration * (setTime / 100)) / 1000;
    audio.currentTime = current;
  };

  // 更新音乐时间和歌词
  const updateTimeAndLyric = () => {
    currentTime.value = audio.currentTime;
    const lyric = getCurrentLyric();
    currentLyric.value = {
      index: lyric.index,
      text: lyric.info.text,
      c_text: lyric.info.c_text || "",
    };
  };

  // 音乐停止处理
  const musicEnd = () => {
    audio.currentTime = 0;
    showToast("音乐播放结束~");
    isPlay.value = false;
  };

  // 获取当前歌词和索引
  const getCurrentLyric = () => {
    const lyricList = currentMusic.value!.LyricList;
    let index = lyricList.length - 1;
    for (let i = 0; i < lyricList.length; i++) {
      if (lyricList[i].time > currentTime.value * 1000) {
        index = i - 1;
        break;
      }
    }
    return {
      info: lyricList[index],
      index,
    };
  };

  // 整合获取音乐信息
  const getMusicData = async (id: number) => {
    await getMusicDetailData(id);
    await getMusicPlayData(id);
    await getMusicLyricData(id);
  };

  // 获取歌曲详细信息
  const getMusicDetailData = async (id: number): Promise<number> => {
    return new Promise((resolve) => {
      getMusicDetailById(id).then((res) => {
        if (!musicHistoryList.value.map((item) => item.id).includes(id)) musicHistoryList.value.unshift(res.songs[0]);
        currentMusic.value = {
          id,
          name: res.songs[0].name,
          picUrl: res.songs[0].al.picUrl,
          duration: res.songs[0].dt,
          singer: res.songs[0].ar[0].name,
          playUrl: "",
          LyricList: [],
        };
        resolve(res.songs[0].mv);
      });
    });
  };

  // 获取音乐播放 url
  const getMusicPlayData = async (id: number) => {
    return getMusicPlayUrl(id).then((res) => {
      currentMusic.value!.playUrl = res.data[0].url;
    });
  };

  // 获取音乐歌词
  const getMusicLyricData = async (id: number) => {
    return getMusicLyric(id).then((res) => {
      let lyricText = res.lrc.lyric,
        t_lyricText = res.tlyric?.lyric,
        lyricList = parseLyric(lyricText);
      currentMusic.value!.LyricList = t_lyricText ? composeCLyrics(lyricList, parseLyric(t_lyricText)) : lyricList;
    });
  };

  return {
    loadMusicPlayer,
    stopMusic,
    startMusic,
    skipMusic,
    currentTime,
    currentFormat,
    currentLyric,
    currentMusic,
    musicHistoryList,
    recommandMusicList,
    isPlay,
  };
});

export default usePlayerStore;
